<!DOCTYPE html>
<html>
<head>
    <title></title>
    <meta charset="utf-8"/>
   	<style type="text/css">
   		canvas{ border: 1px solid #000000;}
   	</style>
</head>
<body>
    <canvas width="600" height="400" id="canva"></canvas>
<body>
</html>
<script type="text/javascript">
	var foods = new Array();    //存放食物坐标
	var gameover = false;
	var gridWidth = 10;
	var canvas = document.getElementById("canva");
	var ctx = canvas.getContext("2d");
	var food_interval,snake_interval,Farm,Snake;
	//定义方块基础对象
	function node(x,y,w)
	{
		var t = this;
		t.x=x;
		t.y=y;
		t.w=w;
		
		//判断是否与其他方块是否重合
		t.equals=function(node){
			if(t.x==node.x && t.y==node.y){
				return true;
			}
			return false;
		}
		
		//初始化为一个食物
		t.foodInit=function(){
			ctx.fillStyle="#FF0000";
			ctx.fillRect(x,y,w,w);
		}
		
		//初始化为一条蛇
		t.snakeInit = function(){
			ctx.fillStyle="#000000";
			ctx.strokeStyle="#FFFFFF";
			ctx.fillRect(x,y,w,w);
			ctx.strokeRect(x,y,w,w);
		}
		//清除本格子
		t.clear = function(){
			ctx.fillStyle="#E8FFFF";
			ctx.strokeStyle="#E8FFFF";
			ctx.fillRect(x,y,w,w);
			ctx.strokeRect(x,y,w,w);
		}
	}
	
	//定义一个场景类
	function farm()
	{
		var t= this;
		ctx.fillStyle="#E8FFFF";
		ctx.fillRect(0,0,canvas.width,canvas.height);

		t.addFood = function(){
			if(gameover){
				return gameOver();
			}else{
				//计算随机位置
				var x = parseInt(canvas.width/gridWidth*Math.random())*gridWidth;
				var y = parseInt(canvas.height/gridWidth*Math.random())*gridWidth;
				var food = new node(x,y,gridWidth);
				food.foodInit();
				foods.push(food);
			}
		}
	}        
	function snake(x,y,len,speed)
	{
		var t = this;
		t.init = function(){
			t.len = len;//身体长度
			t.nodes = new Array();//身体节点
			t.dir = "R";//当前方向
			t.speed = parseInt(speed);//爬行速度
			//从右往左，逐格把蛇画出来
			var nx=x,ny=y;
			for(var i=0;i<len;i++){
				var tmpNode = new node(nx,ny,gridWidth);
				t.nodes[i]=tmpNode;
				tmpNode.snakeInit();
				nx -= gridWidth;
			}
			snake_interval = setInterval(t.move,t.speed);
			//绑定键盘事件
			document.onkeydown = function (e){
				var code = e.keyCode;
				t.odir = t.dir;//记录下之前的方向（主要用于禁止反方向运动）
				switch(code){
					case 65:t.dir = "L";break;
					case 87:t.dir = "U";break;
					case 68:t.dir = "R";break;
					case 83:t.dir = "D";break;
					case 37:t.dir = "L";break;
					case 38:t.dir = "U";break;
					case 39:t.dir = "R";break;
					case 40:t.dir = "D";break;
				}
			}
		}
		
		t.move = function(){
			var len = t.len;
			var head = t.nodes[0];//头部
			switch(t.dir){
				case "R":
					if(head.x+head.w>=canvas.width){
						return gameOver();
					}else{
						var newHead = new node(head.x+head.w,head.y,head.w);
					}
					break;
				case "L":
					if(head.x-head.w<0){
						return gameOver();
					}
					else{
						var newHead = new node(head.x-head.w,head.y,head.w);
					}
					break;
				case "U":
					if(head.y-head.w<0){
						return gameOver();
					}
					else{
						var newHead = new node(head.x,head.y-head.w,head.w);
					}
					break;
				case "D":
					if(head.y+head.w>canvas.height){
						return gameOver();
					}
					else{
						var newHead = new node(head.x,head.y+head.w,head.w);
					}
					break;
			}
			
			//禁止运行反方向
			if(t.nodes[1].equals(newHead)){
				t.dir=t.odir;
				return;
			}
			
			//禁止穿过自身，否则gameover
			for(var i=0;i<t.len;i++){
				if(t.nodes[i].equals(newHead)){
					return gameOver();
				}
			}
			//初始化为蛇头
			newHead.snakeInit();
			//同时把蛇尾去掉
			t.nodes[t.len-1].clear();
			t.nodes.pop();
			
			//蛇身向前走
			for(var i=len-1;i>0;i--)
			{
				t.nodes[i] = t.nodes[i-1];
			}
			t.nodes[0] = newHead;
			
			//判断是否吃到食物
			for(var i=0;i<foods.length;i++)
			{
				if(foods[i].equals(newHead)){
					t.addNode();
					foods.pop(newHead);
					t.speed = t.speed>20?t.speed-10:t.speed;
					clearInterval(snake_interval);
					snake_interval = setInterval(Snake.move,t.speed);
					break;
				}
			}
			
			
		}
		t.addNode = function(){
			var tail1 = t.nodes[t.len-1];
			var tail2 = t.nodes[t.len-2];
			if(tail1.x==tail2.x){
				var addNode;
				if(tail1.y>tail2.y)  addNode = new node(tail1.x,tail1.y2+gridWidth,gridWidth);
				else addNode = new node(tail1.x,tail1.y-gridWidth,gridWidth);
			}else{
				var addNode;
				if(tail1.x>tail2.x)  addNode = new node(tail1.x+gridWidth,tail1.y,gridWidth);
				else addNode = new node(tail1.x-gridWidth,tail1.y,gridWidth);
			}
			addNode.snakeInit();
			t.nodes[t.len]=addNode;
			t.len+=1;
		}
		
	}    
	function gameOver(){
		gameover=true;//标记游戏结束
		//停止添加食物和蛇的跑动
		clearInterval(snake_interval);
		clearInterval(food_interval);
		var res= confirm("游戏结束，是否重新开始");
		while(!res){
			res= confirm("游戏结束，是否重新开始"); 
		}
		gameStart();
		return false;
	}
	function gameStart(){
		foods = new Array();    //存放食物坐标
		gameover = false
		//初始化场地
		Farm = new farm();

		//添加定时器，定时增加食物
		food_interval = setInterval(Farm.addFood,3000);
		
		//初始化一条蛇出来
		Snake = new snake(200,200,5,150);
		
		Snake.init();
	}
	
	gameStart();
</script>